package com.webserver.core;

import com.webserver.annotation.Controller;
import com.webserver.annotation.RequestMapping;

import java.io.File;
import java.lang.reflect.Method;
import java.net.URISyntaxException;
import java.util.HashMap;
import java.util.Map;

/**
 * 使用当前类维护请求路径与对应的Controller中处理该请求的方法
 * 使得DispatcherServlet在处理请求时判断是否为业务可以使用当前类完成。
 */


public class HandlerMapping {
    private static Map<String,MethodMapping> mapping = new HashMap<>();

    static {
        initMapping();
    }

    private static void initMapping(){
        try {
            File rootDir = new File(HandlerMapping.class.getClassLoader().getResource(".").toURI());
            System.out.println( "rootDir的内容：" + rootDir);//rootDir的内容：C:\Users\Administrator\IdeaProjects\WebServer\V28\target\classes

            //获取controller文件夹的绝对路径
            File dir = new File(rootDir,"/com/webserver/controller");
            System.out.println( "dir的内容：" + dir);//dir的内容：C:\Users\Administrator\IdeaProjects\WebServer\V28\target\classes\com\webserver\controller
            System.out.println( "dir的getName内容：" + dir.getName());//dir的getName内容：controller

            //根据controller的绝对路径，对绝对路径使用getName方法获取最后\的内容
            File[] files = dir.listFiles(f->f.getName().endsWith(".class"));//listFiles方法不改变原来dir的内容
            for (File f : files){
                System.out.println( "f的内容：" + f);//f的内容：C:\Users\Administrator\IdeaProjects\WebServer\V28\target\classes\com\webserver\controller\ArticleController.class
                String fileName = f.getName();
                System.out.println( "fileName的内容：" + fileName);//fileName的内容：UserController.class
                String className = fileName.split("\\.")[0];
                Class c = null;
                    //包名+类名(去掉.class部分)
                    c = Class.forName("com.webserver.controller."+className);
                    if(c.isAnnotationPresent(Controller.class)){//判断是否是注释方法
                        Method[] methods = c.getMethods();
                        for (Method m : methods){
                            if(m.isAnnotationPresent(RequestMapping.class)){//判断是否是注释方法
                                RequestMapping rm = m.getAnnotation(RequestMapping.class);//获取方法上的注释对象
                                String value = rm.value();//通过注释对象的value()将方法上注释的内容得到.
                                Object controller = c.newInstance();//新建的类
                                MethodMapping mm = new MethodMapping(m,controller);//将方法和新建的类作为参数传入MethodMapping实例中
                                mapping.put(value,mm);//将注释的内容作为Key.

                            }
                        }
                    }
            }
        } catch (URISyntaxException e) {
            e.printStackTrace();
        } catch (ClassNotFoundException e) {
            e.printStackTrace();
        }catch (InstantiationException e) {
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            e.printStackTrace();
        }


    }

    public static MethodMapping getMethod(String uri){
        return mapping.get(uri);
    }




    public static class MethodMapping{
        private Method method;
        private Object object;

        public MethodMapping(Method method,Object object){
            this.method = method;
            this.object = object;
        }

        public Method getMethod() {
            return method;
        }

        public Object getObject() {
            return object;
        }
    }
}

